import { createElements, css, define, itag } from "../itag/index.js";
import { createOption } from "./createElement.js";
import { CustomRequestFieldElement } from "./CustomRequestFieldElement.js";
import type { IRequestFieldElement } from "./IFieldElement.js";
import { type RequestFieldOption } from "./RequestOption.js";
import * as styles from "./styles.js";

const sheet = css`
    :host {
        display: block;

        .container {
            display: flex;
            flex-wrap: wrap;
            margin-top: 1em;
        }

        .group {
            text-align: center;
            padding: 0 0.6em;
        }

        .h-spacer {
            height: 0.6em;
        }

        button {
            width: 80%;
        }

        .send {
            width: 100%;
            font-size: inherit;
        }
    }
`;

export interface RequestDetailElement {
    addEventListener(
        type: "submit",
        listener: (this: this, ev: CustomEvent<{ api: string; data: number[] }>) => void,
        options?: boolean | AddEventListenerOptions
    ): void;

    addEventListener(
        type: string,
        listener: EventListenerOrEventListenerObject,
        options?: boolean | AddEventListenerOptions
    ): void;
}

export class RequestDetailElement extends HTMLElement {
    /** 当前的 api */
    #api: string = "";

    readonly #elms = createElements({
        title: "h3",
        content: "div",
        description: "p",
        send: "button",
    });

    #fields: IRequestFieldElement[] = [];

    constructor() {
        super();
        const sr = this.attachShadow({ mode: "open" });
        sr.adoptedStyleSheets.push(sheet, styles.sheet);

        itag`
${sr}
    ${this.#elms.title} 
    ${this.#elms.description} 
    div .h-spacer
    ${this.#elms.content} .container
    div .h-spacer
    div
        ${this.#elms.send} .send : 发送
`;

        this.#elms.send.addEventListener("click", () => {
            const data = this.#data();
            this.dispatchEvent(new CustomEvent("submit", { detail: { api: this.#api, data } }));
        });
    }

    add(option: RequestFieldOption) {
        const group = createOption(option);
        group.setBegin(this.#length());
        group.addEventListener("change", () => {
            this.#updateCustom();
        });

        this.#elms.content.appendChild(group);
        this.#fields.push(group);
        this.#updateCustom();
    }

    set api(value: string) {
        this.#api = value;
        this.#elms.title.textContent = this.#api;
    }

    set description(value: string | undefined) {
        this.#elms.description.textContent = value ?? "";
    }

    /**
     * 数据
     */
    #data(): number[] {
        const data = [];
        for (const group of this.#fields) {
            data.push(...group.data());
        }
        return data;
    }

    #length(): number {
        let len = 0;
        for (const group of this.#fields) {
            len += group.byteLength();
        }
        return len;
    }

    /**
     * 重置
     */
    reset() {
        this.#elms.content.innerHTML = "";
        this.#fields = [];
    }

    /**
     * 更新自定义字段
     */
    #updateCustom() {
        const lengths: Record<string, number> = Object.create(null);
        for (const field of this.#fields) {
            lengths[field.name] = field.byteLength();
        }
        for (const field of this.#fields) {
            if (field instanceof CustomRequestFieldElement) {
                field.update({ lengths });
            }
        }
    }
}

define(RequestDetailElement);
